package ar.edu.unq.sandsoft.constructors;

import java.io.IOException;
import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.Map;

import javax.xml.parsers.ParserConfigurationException;

import org.xml.sax.SAXException;

import ar.edu.unq.sandsoft.exceptions.CouldnFindAttribute;

public class ClassConstructor {

    private static final String GET = "get";

    private static final String SET = "set";

    private String className;

    private Map<String, String> assoc;

    public ClassConstructor(final Map<String, String> assoc, final String className) {
        this.assoc = assoc;
        this.className = className;
    }

    public Map<String, Method> prepareSetters() throws ClassNotFoundException, SecurityException, NoSuchMethodException {
        Class<?> constructed = Class.forName(className);
        Map<String, Method> methodAsoc = new HashMap<String, Method>();
        for (String bean : assoc.keySet()) {
            Class<?> typeClass = Class.forName(assoc.get(bean));
            methodAsoc.put(bean, constructed.getMethod(SET + toUpperFirst(bean), new Class[] { typeClass }));
        }
        return methodAsoc;
    }

    public Map<String, Method> prepareGetters() throws ClassNotFoundException, SecurityException, NoSuchMethodException {
        Class<?> constructed = Class.forName(className);
        Map<String, Method> methodAsoc = new HashMap<String, Method>();
        for (String bean : assoc.keySet()) {
            methodAsoc.put(bean, constructed.getMethod(GET + toUpperFirst(bean), new Class[] {}));
        }
        return methodAsoc;
    }

    public Object instance() throws SAXException, IOException, ParserConfigurationException, CouldnFindAttribute,
            SecurityException, ClassNotFoundException, NoSuchMethodException, InstantiationException,
            IllegalAccessException {
        Class<?> clazz = Class.forName(this.className);
        return clazz.newInstance();

    }

    private String toUpperFirst(String bean) {
        char[] chars = bean.toCharArray();
        String first = String.valueOf(chars, 0, 1);
        String rest = String.valueOf(chars, 1, chars.length - 1);

        return first.toUpperCase().concat(rest);
    }
}
